// useAgoraRTC.ts
import { shallowRef, shallowReactive, onUnmounted } from "vue";
import AgoraRTC, {
  ClientRole,
  type IAgoraRTCClient,
  type ILocalAudioTrack,
} from "agora-rtc-sdk-ng";
import { ElMessage } from "element-plus";

type PublishedTracks = {
  localSystemAudioTrack: ILocalAudioTrack | null;
  microphoneTrack: ILocalAudioTrack | null;
};

const options = {
  APP_ID: "4487c53bb8a548508ffe17fceb321334",
  TOKEN:
    "007eJxTYBA/FH3zhU2TKGfY+SNlfOKb2xUED/n2b2CY9SUmeVHSh/0KDCYmFubJpsZJSRaJpiYWpgYWaWmphuZpyalJxkaGxsYmlp//pjcEMjK4n3vLwsgAgSA+J0NZfmZyalB+fi4DAwDOtCHf",
  U_ID: "56988",
  CHANNEL: "voiceRoom",
};

export default function useAgoraRTC() {
  // 浅层响应式状态
  const client = shallowRef<IAgoraRTCClient | null>(null);
  const localTracks = shallowReactive<PublishedTracks>({
    localSystemAudioTrack: null,
    microphoneTrack: null,
  });
  const isJoined = shallowRef(false);
  const isHost = shallowRef(false);

  // 初始化客户端
  const initClient = async () => {
    // const { AgoraRTC } = await import("agora-rtc-sdk-ng");
    try {
      client.value = AgoraRTC.createClient({ mode: "live", codec: "vp8" });
      ElMessage.success("客户端初始化成功");
    } catch (error) {
      ElMessage.error("客户端初始化失败: " + error);
      throw error;
    }
  };

  // 设置用户角色 (核心权限控制)
  const setClientRole = async (role: ClientRole) => {
    if (!client.value) {
      ElMessage.warning("客户端未初始化");
      return;
    }

    try {
      await client.value.setClientRole(role);
      isHost.value = role === "host";
      ElMessage.success(`角色已设置为: ${role}`);
    } catch (error) {
      ElMessage.error("角色设置失败: " + error);
      throw error;
    }
  };

  // 加入频道
  const joinChannel = async () => {
    if (!client.value) {
      ElMessage.warning("请先初始化客户端");
      return;
    }

    try {
      await client.value.join(options.APP_ID, options.CHANNEL, options.TOKEN);
      isJoined.value = true;
      ElMessage.success("加入频道成功");

      // 自动订阅逻辑
      client.value.on("user-published", async (user, mediaType) => {
        await client.value?.subscribe(user, mediaType);
        if (mediaType === "audio") {
          user.audioTrack?.play();
          ElMessage.success("已订阅远端用户音频");
        }
      });

      client.value.on("user-unpublished", async (user) => {
        await client.value?.unsubscribe(user);
      });
    } catch (error) {
      ElMessage.error("加入频道失败: " + error);
      throw error;
    }
  };

  // 推流（上麦）
  const publishStream = async () => {
    if (!client.value || !isHost.value) {
      ElMessage.warning("当前不是主播状态");
      return;
    }

    try {
      // 获取系统音频
      const stream = await navigator.mediaDevices.getUserMedia({ audio: true });
      const systemTrack = stream.getAudioTracks()[0];

      // 创建音轨
      const [microphoneTrack, localSystemTrack] = await Promise.all([
        AgoraRTC.createMicrophoneAudioTrack(),
        AgoraRTC.createCustomAudioTrack({ mediaStreamTrack: systemTrack }),
      ]);

      // 发布音轨
      await client.value.publish([microphoneTrack, localSystemTrack]);

      // 保存音轨引用
      localTracks.microphoneTrack = microphoneTrack;
      localTracks.localSystemAudioTrack = localSystemTrack;

      ElMessage.success("推流成功");
    } catch (error) {
      ElMessage.error("推流失败: " + error);
      throw error;
    }
  };

  // 离开频道（下麦）
  const leaveChannel = async () => {
    if (!client.value) return;

    try {
      // 取消发布音轨
      if (localTracks.localSystemAudioTrack) {
        await client.value.unpublish(localTracks.localSystemAudioTrack);
        localTracks.localSystemAudioTrack.close();
      }
      if (localTracks.microphoneTrack) {
        await client.value.unpublish(localTracks.microphoneTrack);
        localTracks.microphoneTrack.close();
      }

      // 离开频道
      await client.value.leave();

      // 重置状态
      isJoined.value = false;
      isHost.value = false;
      localTracks.localSystemAudioTrack = null;
      localTracks.microphoneTrack = null;

      ElMessage.success("已离开频道");
    } catch (error) {
      ElMessage.error("离开频道失败: " + error);
      throw error;
    }
  };

  // 自动清理
  onUnmounted(async () => {
    if (isJoined.value) {
      await leaveChannel();
    }
  });

  return {
    client,
    localTracks,
    isJoined,
    isHost,
    initClient,
    setClientRole,
    joinChannel,
    publishStream,
    leaveChannel,
  };
}
